﻿using SuperX.Common.Helper;
using SuperX.Common.Log;
using System;
using System.Collections.Generic;
using System.IO;
using System.Text;

namespace SuperX.Common.Respository
{
    // 
    public class JsonRepository : IRepository
    {
        // 
        public object Model { get; set; }

        // 
        public string FilePath { get; set; }

        // 
        public bool IsEncrypt { get; set; }

        // 
        public JsonRepository()
        {
        }

        // 
        public JsonRepository(string fileFullPath)
        {
            this.FilePath = fileFullPath;
        }

        //
        public JsonRepository(string fileFullPath, object model, bool isEncrypt = false)
        {
            this.FilePath = fileFullPath;
            this.Model = model;
            this.IsEncrypt = isEncrypt;
        }

        // 
        public void Load(Type type)
        {
            if (string.IsNullOrEmpty(this.FilePath))
            {
                throw new ArgumentNullException("File full path is empty");
            }
            string text = this.FilePath + ".bak";
            if (File.Exists(this.FilePath) && this.CanLoad(this.FilePath, type))
            {
                this.Model = this._model;
                return;
            }
            if (File.Exists(text) && this.CanLoad(text, type))
            {
                this.Model = this._model;
            }
        }

        // 
        private bool CanLoad(string fileName, Type type)
        {
            bool flag = true;
            if (this.IsEncrypt)
            {
                try
                {
                    this._model = JsonHelper.JsonDeserializeFromFile(this.FilePath, type, Encoding.UTF8, "");
                }
                catch (Exception)
                {
                    flag = false;
                }
                if (flag)
                {
                    return true;
                }
                try
                {
                    this._model = JsonHelper.JsonDeserializeFromFile(this.FilePath, type, Encoding.UTF8);
                    flag = true;
                }
                catch (Exception)
                {
                    flag = false;
                }
                return flag;
            }
            else
            {
                try
                {
                    this._model = JsonHelper.JsonDeserializeFromFile(this.FilePath, type, Encoding.UTF8);
                }
                catch (Exception ex)
                {
                    Logger.Error(ex.Message);
                    flag = false;
                }
                if (flag)
                {
                    return true;
                }
                try
                {
                    this._model = JsonHelper.JsonDeserializeFromFile(fileName, type, Encoding.UTF8, "");
                    flag = true;
                }
                catch (Exception ex2)
                {
                    Logger.Error(ex2.Message);
                    flag = false;
                }
                return flag;
            }
        }

        // 
        public void Save()
        {
            string fullPath = Path.GetFullPath(this.FilePath);
            string text = fullPath + ".bak";
            string directoryName = Path.GetDirectoryName(text);
            string text2 = null;
            try
            {
                if (directoryName != null && !Directory.Exists(directoryName))
                {
                    Directory.CreateDirectory(directoryName);
                }
                if (File.Exists(fullPath))
                {
                    File.Copy(fullPath, text, true);
                }
                if (this.IsEncrypt)
                {
                    text2 = JsonHelper.JsonSerializeToFile(this.Model, fullPath, Encoding.UTF8, "");
                }
                else
                {
                    text2 = JsonHelper.JsonSerializeToFile(this.Model, fullPath, Encoding.UTF8);
                }
            }
            catch (Exception ex)
            {
                Logger.Error(ex.Message + Environment.NewLine + ex.StackTrace);
            }
            if (!File.Exists(fullPath))
            {
                throw new Exception(fullPath + "save failed");
            }
            if (text2 != null && File.ReadAllText(fullPath) == text2)
            {
                File.Delete(text);
                return;
            }
            File.Delete(fullPath);
            if (File.Exists(text))
            {
                File.Copy(text, fullPath, true);
            }
            throw new Exception(fullPath + "save failed");
        }

        // 
        private object _model;
    }
}
